using System;
using System.Collections.Generic;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading.Tasks;

namespace SharpSoft.Net.P2P
{
    public class TcpPeerServer : TcpPeer
    {
        private int defaultbacklog = 200;
        protected bool islistening = false;
        public TcpPeerServer() : base()
        {

        }
        public TcpPeerServer(IPEndPoint listenep) : base(listenep)
        {

        }
        public TcpPeerServer(string listenhost, int listenport) : base(listenhost, listenport)
        {

        }
        public TcpPeerServer(IPAddress listenhost, int listenport) : base(listenhost, listenport)
        {

        }
        public TcpPeerServer(int listenport) : base(listenport)
        {

        }
        public override void Disconnect(bool reuse)
        {
            islistening = false;
            base.Disconnect(reuse);
        }
        public void Listen()
        {
            this.Listen(defaultbacklog);
        }
        public void Listen(int backlog)
        {
            Socket.Listen(backlog);
            islistening = true;
            isworking = true;
        }
        public async Task<TcpPeer> AcceptTCPPeerAsync()
        {
            return await Task<TcpPeer>.Run(new Func<TcpPeer>(this.AcceptTCPPeer));
        }

        public TcpPeer AcceptTCPPeer()
        {
            var socket = Socket.Accept();
#if DEBUG
            Console.WriteLine($"[{socket.RemoteEndPoint}]tcp客户端已连接。");
#endif

            //socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
            return new TcpPeer(socket);
        }

        public void AcceptTCPPeerWith(Action<TcpPeer> action)
        {
            if (!this.islistening)
            {
                throw new Exception("当前peerService尚未开始监听，无法开始接入客户端。");
            }
            Task.Run(delegate
            {
                while (this.islistening)
                {
                    var peer = this.AcceptTCPPeer();
                    action?.Invoke(peer);
                }
            });
        }


    }
}
